package cn.com.yx.ms.service.impl;

import cn.com.yx.ms.application.web.ApiPager;
import cn.com.yx.ms.application.web.ApiQueryBase;
import cn.com.yx.ms.domain.GlobalConfigModel;
import cn.com.yx.ms.domain.MenuModel;
import cn.com.yx.ms.domain.TestModel;
import cn.com.yx.ms.domain.dbmodel.*;
import cn.com.yx.ms.domain.sys.*;
import cn.com.yx.ms.persistence.*;
import cn.com.yx.ms.service.ICommonService;
import cn.com.yx.ms.service.ILogService;
import cn.com.yx.ms.service.ISysService;
import cn.com.yx.ms.service.IUserContextService;
import cn.yx.framework.configuration.ApiCode;
import cn.yx.framework.configuration.AppConstant;
import cn.yx.framework.configuration.RegexConstant;
import cn.yx.framework.context.UserContext;
import cn.yx.framework.security.Des3Kit;
import cn.yx.framework.util.DateUtil;
import cn.yx.framework.util.DesUtils;
import cn.yx.framework.view.ApiResult;
import com.alibaba.fastjson.JSON;
import com.github.pagehelper.Page;
import com.github.pagehelper.PageHelper;
import com.github.pagehelper.util.StringUtil;
import com.google.code.kaptcha.Producer;
import org.apache.commons.lang3.StringUtils;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import sun.misc.BASE64Encoder;

import javax.annotation.Resource;
import javax.imageio.ImageIO;
import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.awt.image.BufferedImage;
import java.io.ByteArrayOutputStream;
import java.security.MessageDigest;
import java.util.*;
import java.util.concurrent.TimeUnit;

/**
 * ApphubServiceImpl
 */
@Service
@Transactional
public class SysServiceImpl implements ISysService {

    @Resource
    private ILogService iLogService;
    @Resource
    private IUserContextService iUserContextService;
    @Resource
    private TestMapper testMapper;
    @Resource
    private SysOrgMapper sysOrgMapper;
    @Resource
    private SysUserMapper sysUserMapper;
    @Resource
    private SysRoleMapper sysRoleMapper;
    @Resource
    private SysRoleUserMapMapper sysRoleUserMapMapper;
    @Resource
    private SysRoleFunMapMapper sysRoleFunMapMapper;
    @Resource
    private SysMenuMapper sysMenuMapper;
    @Resource
    private SysConfigMapper sysConfigMapper;
    @Resource
    private ICommonService iCommonService;
    @Resource
    private RedisTemplate redisTemplate;
    @Resource
    private Producer captchaProducer = null;

    private static final String GLOBAL_CONFIG_ID = "globalconfig";

    @Override
    public TestModel findOne(String id) {
        System.out.println("无缓存时走这里...");
        return testMapper.findOne(id);
    }

    @Override
    public int insert(TestModel testModel) {
        return testMapper.insert(testModel);
    }

    @Override
    public int delete(String id) {
        return testMapper.delete(id);
    }

    @Override
    public int update(TestModel testModel) {
        return testMapper.update(testModel);
    }

    @Override
    public ApiPager<TestModel> find(ApiQueryBase query) {

        PageHelper.startPage(query.getPi(), query.getPs(), true);
        Page<TestModel> page = (Page<TestModel>) testMapper.find(query);

        ApiPager<TestModel> apiPager = new ApiPager<TestModel>(query.getPs(),
                query.getPi(),
                page.getTotal(),
                page.getResult());
        return apiPager;//ApiResult.success(AppConstant.MSG_SUCCESS, apiPager);

    }

    // region << 公共方法 >>
    public ValidImgModel gengrateValidCode(HttpServletResponse response) throws Exception {
        ValidImgModel result = new ValidImgModel();

        response.setDateHeader("Expires", 0);
        response.setHeader("Cache-Control", "no-store, no-cache, must-revalidate");
        response.addHeader("Cache-Control", "post-check=0, pre-check=0");
        response.setHeader("Pragma", "no-cache");
        response.setHeader("Access-Control-Allow-Credentials", "true");
        response.setContentType("image/jpeg");

        String capText = captchaProducer.createText();
        System.out.println("capText: " + capText);

        String uuid = "";
        try {
            uuid = UUID.randomUUID().toString();
            redisTemplate.opsForValue().set(uuid, capText, 60 * 5, TimeUnit.SECONDS);
            Cookie cookie = new Cookie("captchaCode", uuid);
            response.addCookie(cookie);
        } catch (Exception e) {
            e.printStackTrace();
        }

        BufferedImage img = captchaProducer.createImage(capText);
        final ByteArrayOutputStream os = new ByteArrayOutputStream();
        ImageIO.write(img, "jpg", os);
        result.setUuid(uuid);
        result.setImgbase64(Base64.getEncoder().encodeToString(os.toByteArray()));
        return result;
    }

    public String getValidCode(String redisKey) {
        String validCode = (String) redisTemplate.opsForValue().get(redisKey);
        return validCode;
    }
    // endregion

    //region << 部门管理 >>
    @Override
    public ApiResult saveOrg(OrgModel orgModel) {
        ApiResult result = null;


        if (!StringUtils.isNoneBlank(orgModel.getName())) {
            result = new ApiResult(AppConstant.MSG_FAILURE, false, "部门名称不能为空");
        }

        if (!StringUtils.isNoneBlank(orgModel.getOrgcode())) {
            result = new ApiResult(AppConstant.MSG_FAILURE, false, "部门编码不能为空");
        }

        //判断部门编码是否重复
        int countByOrgCode = sysOrgMapper.selectCountByOrgCode(orgModel.getOrgcode());
        if (!StringUtils.isNoneBlank(orgModel.getId()) && countByOrgCode > 0) {
            result = new ApiResult(AppConstant.MSG_FAILURE, false, "部门编码已存在，请重新输入");
        }

        if (!StringUtils.isNoneBlank(orgModel.getId())) {
            result = new ApiResult().success(AppConstant.MSG_SUCCESS, "", insertOrg(orgModel));

        } else {
            result = new ApiResult().success(AppConstant.MSG_SUCCESS, "", updateOrg(orgModel));

        }

        return result;
    }

    @Override
    public int insertOrg(OrgModel orgModel) {
        SysOrg sysOrg = new SysOrg();

        if (!StringUtils.isNoneBlank(orgModel.getId())) {
            orgModel.setId(UUID.randomUUID().toString());
        }

        sysOrg.setGuid(orgModel.getId());
        sysOrg.setOrgname(orgModel.getName());
        sysOrg.setOrgcode(orgModel.getOrgcode());
        sysOrg.setParentid(orgModel.getParentid());
        sysOrg.setNumber(iCommonService.getMaxNumber(orgModel.getParentid()));
        sysOrg.setOrderindex(orgModel.getOrderindex());
        sysOrg.setCreatetime(new Date());
        sysOrg.setMemo("");
        sysOrg.setIsdeleted(0);
        int result = sysOrgMapper.insert(sysOrg);
        if (result > 0) {

            iLogService.log("info",
                    "部门管理",
                    "创建成功-【" + JSON.toJSONString(sysOrg) + "】",
                    iUserContextService.getUserContext().getId());
        }
        return result;
    }

    @Override
    public int deleteOrg(String id) {
        SysOrg org = sysOrgMapper.selectByPrimaryKey(id);

        int result = 0;
        if (org != null) {
            // result = sysOrgMapper.deleteByPrimaryKey(id);
            org.setIsdeleted(1);
            sysOrgMapper.updateByPrimaryKey(org);
            //伪删除部门人员
            sysUserMapper.updateByOrgid(id);
            if (result > 0) {
                iLogService.log("info",
                        "部门管理",
                        "删除成功-【" + id + "】-【" + org.getOrgname() + "】",
                        iUserContextService.getUserContext().getId());
            }
        }
        return result;
    }


    @Override
    public int updateOrg(OrgModel orgModel) {
        SysOrg sysOrg = sysOrgMapper.selectByPrimaryKey(orgModel.getId());
        sysOrg.setOrgname(orgModel.getName());
        sysOrg.setOrgcode(orgModel.getOrgcode());
        sysOrg.setOrderindex(orgModel.getOrderindex());
        sysOrg.setMemo("");
        sysOrg.setIsdeleted(0);
        int result = sysOrgMapper.updateByPrimaryKey(sysOrg);
        if (result > 0) {
            iLogService.log("info",
                    "部门管理",
                    "修改成功-【" + JSON.toJSONString(sysOrg) + "】",
                    iUserContextService.getUserContext().getId());
        }
        return result;
    }

    @Override
    public List<OrgModel> findOrg(ApiQueryBase apiQueryBase) {
        List<SysOrg> sysOrgs = sysOrgMapper.find(apiQueryBase);
        List<OrgModel> orgModels = new ArrayList<OrgModel>();

        //初始化根节点
        OrgModel root = new OrgModel();
        root.setId("root");
        root.setName("组织结构");
        root.setNumber("");
        root.setChildren(new ArrayList<OrgModel>());

        BuildOrgTree(root, sysOrgs);

        if (root.getChildren() != null && root.getChildren().size() != 0) {
            root.setIsleaf(0);
        } else {
            root.setIsleaf(1);
        }

        orgModels.add(root);
        return orgModels;
    }

    private void BuildOrgTree(OrgModel node, List<SysOrg> sysOrgs) {
        for (SysOrg sysOrg :
                sysOrgs) {
            if (sysOrg.getParentid() != null && sysOrg.getParentid().equals(node.getId())) {
                OrgModel child = new OrgModel();
                child.setId(sysOrg.getGuid());
                child.setName(sysOrg.getOrgname());
                child.setParentid(sysOrg.getParentid());
                child.setNumber(sysOrg.getNumber());

                child.setOrderindex(sysOrg.getOrderindex());
                child.setChildren(new ArrayList<OrgModel>());
                node.getChildren().add(child);

                //递归调用
                BuildOrgTree(child, sysOrgs);
                if (child.getChildren() != null && child.getChildren().size() != 0) {
                    child.setIsleaf(0);
                } else {
                    child.setIsleaf(1);
                }
            }

        }

    }

    @Override
    public OrgModel findOneOrg(String id) {
        OrgModel orgModel = null;
        SysOrg sysOrg = sysOrgMapper.selectByPrimaryKey(id);
        if (sysOrg != null) {
            orgModel = new OrgModel();
            orgModel.setId(sysOrg.getGuid());
            orgModel.setParentid(sysOrg.getParentid());
            orgModel.setName(sysOrg.getOrgname());
            orgModel.setOrgcode(sysOrg.getOrgcode());
            orgModel.setOrderindex(sysOrg.getOrderindex());
            orgModel.setMemo(sysOrg.getMemo());
        }
        return orgModel;
    }

    //endregion

    // region << 用户管理 >>

    @Override
    public ApiCode saveUser(UserModel userModel) throws Exception {
        ApiCode apiCode = ApiCode.APP_100200;

        // region << 有效性校验 >>
        if (!StringUtils.isNoneBlank(userModel.getCname())) {
            apiCode = ApiCode.APP_121503;
            return apiCode;
        }
        if (!StringUtils.isNoneBlank(userModel.getEname())) {
            apiCode = ApiCode.APP_121504;
            return apiCode;
        }
        // 手机号校验
        if (StringUtils.isNoneBlank(userModel.getMobile())) {
            if (!RegexConstant.match(RegexConstant.Mobile, userModel.getMobile())) {
                apiCode = ApiCode.APP_121505;
                return apiCode;
            }
        }
        // 邮箱校验
        if (StringUtils.isNoneBlank(userModel.getEmail())) {
            if (!RegexConstant.match(RegexConstant.EMAIL, userModel.getEmail())) {
                apiCode = ApiCode.APP_121506;
                return apiCode;
            }
        }
        // 判断人员账号是否重复
        int countByEname = sysUserMapper.selectCountByEname(userModel.getEname());
        if (!StringUtils.isNoneBlank(userModel.getGuid()) && countByEname > 0) {
            apiCode = ApiCode.APP_121507;
            return apiCode;
        }
        // endregion

        if (!StringUtils.isNoneBlank(userModel.getGuid())) {
            //result = new ApiResult().success(AppConstant.MSG_SUCCESS, "创建成功", insertUser(userModel));
            if (insertUser(userModel) > 0) {
                apiCode = ApiCode.APP_120500;
            }

        } else {
            // result = new ApiResult().success(AppConstant.MSG_SUCCESS, "修改成功", updateUser(userModel));
            updateUser(userModel);
            apiCode = ApiCode.APP_120501;
        }

        //删除多余角色数据
        sysRoleMapper.deleteNoMapRole();

        return apiCode;
    }

    @Override
    public int insertUser(UserModel userModel) throws Exception {

        SysUser sysUser = new SysUser();

        if (!StringUtils.isNoneBlank(sysUser.getGuid())) {
            userModel.setGuid(UUID.randomUUID().toString());
        }

        sysUser.setGuid(userModel.getGuid());
        sysUser.setCname(userModel.getCname());
        sysUser.setEname(userModel.getEname());
        //sysUser.setPwd("cR/U01DAgvM="); //默认密码123
        sysUser.setPwd(DesUtils.encrypt("123456"));
        sysUser.setCreatetime(new Date());
        sysUser.setOrgid(userModel.getOrgid());
        sysUser.setMemo("");
        sysUser.setIsdeleted(0);
        sysUser.setMobile(userModel.getMobile());
        sysUser.setEmail(userModel.getEmail());

        //保存用户信息
        int result = sysUserMapper.insert(sysUser);
        if (result > 0) {
            updateUserRoles(sysUser.getGuid(), userModel.getRoles());
            iLogService.log("info",
                    "用户管理",
                    "创建成功-【" + JSON.toJSONString(sysUser) + "】",
                    iUserContextService.getUserContext().getId());
        }

        return result;
    }

    @Override
    public int deleteUser(String id) {
        int result = 0;
        SysUser sysUser = sysUserMapper.selectByPrimaryKey(id);

        if (sysUser != null) {
            // result = sysUserMapper.deleteByPrimaryKey(id);
            sysUser.setIsdeleted(1);
            sysUserMapper.updateByPrimaryKey(sysUser);

            if (result > 0) {
                iLogService.log("info",
                        "用户管理",
                        "删除成功-【" + id + "】-【" + sysUser.getCname() + "】",
                        iUserContextService.getUserContext().getId());
            }
        }
        return result;
    }

    @Override
    public int updateUser(UserModel userModel) {
        SysUser sysUser = sysUserMapper.selectByPrimaryKey(userModel.getGuid());
        sysUser.setCname(userModel.getCname());
        sysUser.setEname(userModel.getEname());
        sysUser.setMobile(userModel.getMobile());
        sysUser.setEmail(userModel.getEmail());


        //保存用户信息
        int result = sysUserMapper.updateByPrimaryKey(sysUser);
        if (result > 0) {
            updateUserRoles(sysUser.getGuid(), userModel.getRoles());

            iLogService.log("info",
                    "用户管理",
                    "修改成功-【" + JSON.toJSONString(sysUser) + "】",
                    iUserContextService.getUserContext().getId());
        }

        return result;
    }

    /**
     * 更新用户角色信息
     *
     * @param userId
     * @param roleIds
     */
    private void updateUserRoles(String userId, List<String> roleIds) {
        if (roleIds != null && roleIds.size() > 0) {
            //删除该用户所有角色
            deleteAllRolesByUserId(userId);
            //重新创建该用户角色
            for (String roleId : roleIds) {
                SysRoleUserMap sysRoleUserMap = new SysRoleUserMap();
                sysRoleUserMap.setGuid(UUID.randomUUID().toString());
                sysRoleUserMap.setRoleid(roleId);
                sysRoleUserMap.setUserid(userId);
                sysRoleUserMapMapper.insert(sysRoleUserMap);
            }
        }
    }

    @Override
    public List<SysUser> findUser(ApiQueryBase apiQueryBase) {
        return sysUserMapper.find(apiQueryBase);
    }

    @Override
    public UserModel findOneUser(String id) {
        UserModel userModel = null;
        SysUser sysUser = sysUserMapper.selectByPrimaryKey(id);
        if (sysUser != null) {
            userModel = new UserModel();
            userModel.setGuid(sysUser.getGuid());
            userModel.setCname(sysUser.getCname());
            userModel.setEname(sysUser.getEname());
            userModel.setPwd(sysUser.getPwd());
            userModel.setCreatetime(DateUtil.date2String(sysUser.getCreatetime(), "yyyy-MM-dd HH:mm:ss"));
            userModel.setOrgid(sysUser.getOrgid());
            userModel.setMemo(sysUser.getMemo());
            userModel.setIsdelted(sysUser.getIsdeleted());
            if (sysUser.getOrderindex() == null) {
                userModel.setOrderindex(0);
            } else {
                userModel.setOrderindex(sysUser.getOrderindex());
            }
            userModel.setMobile(sysUser.getMobile());
            userModel.setEmail(sysUser.getEmail());

            List<String> roles = sysRoleUserMapMapper.findRoleIdsByUserId(userModel.getGuid());
            userModel.setRoles(roles);
        }
        return userModel;
    }

    @Override
    public ApiCode updatePwd(UserChangePwdModel userChangePwdModel) throws Exception {
        ApiCode apiCode = ApiCode.APP_100200;

        // region << 有效性校验 >>
        if (userChangePwdModel == null) {
            apiCode = ApiCode.APP_101400;
            return apiCode;
        }

        if (!StringUtils.isNoneBlank(userChangePwdModel.getNewpwd())) {
            // 新密码不能为空
            apiCode = ApiCode.APP_121501;
            return apiCode;
        }
        if (!userChangePwdModel.getNewpwd().equals(userChangePwdModel.getEnnewpwd())) {
            // 新密码和密码确认不匹配
            apiCode = ApiCode.APP_121502;
            return apiCode;
        }

        UserModel userModel = findOneUser(userChangePwdModel.getUserguid());
        if (userModel == null || !userModel.getPwd().equals(DesUtils.encrypt(userChangePwdModel.getOldpwd()))) {
            // 原始密码输入不正确
            apiCode = ApiCode.APP_121500;
            return apiCode;
        }
        // endregion

        SysUser user = sysUserMapper.selectByPrimaryKey(userChangePwdModel.getUserguid());
        if (user != null) {
            user.setPwd(DesUtils.encrypt(userChangePwdModel.getNewpwd()));
            sysUserMapper.updateByPrimaryKey(user);
        }

        return apiCode;
    }
    // endregion

    //region << 角色管理 >>

    @Override
    public ApiResult saveRole(SysRole sysRole) {
        ApiResult result = null;

        if (!StringUtils.isNoneBlank(sysRole.getRolename())) {
            result = new ApiResult(AppConstant.MSG_FAILURE, false, "请输入角色名称");
            return result;
        }

        //判断角色名称是否重复
        int countByRoleName = sysRoleMapper.selectCountByRoleName(sysRole.getRolename());
        if (!StringUtils.isNoneBlank(sysRole.getGuid()) && countByRoleName > 0) {
            result = new ApiResult(AppConstant.MSG_FAILURE, false, "该账号已存在，请重新输入");
            return result;
        }

        if (!StringUtils.isNoneBlank(sysRole.getGuid())) {
            result = new ApiResult().success(AppConstant.MSG_SUCCESS, "", insertRole(sysRole));

        } else {
            result = new ApiResult().success(AppConstant.MSG_SUCCESS, "", updateRole(sysRole));
        }

        return result;
    }

    @Override
    public int insertRole(SysRole sysRole) {
        int result = 0;
        if (!StringUtils.isNoneBlank(sysRole.getGuid())) {
            sysRole.setGuid(UUID.randomUUID().toString());
        }

        sysRole.setCreatetime(new Date());
        sysRole.setIsdeleted(0);
        result = sysRoleMapper.insert(sysRole);
        if (result > 0) {
            iLogService.log("info",
                    "角色管理",
                    "创建成功-【" + JSON.toJSONString(sysRole) + "】",
                    iUserContextService.getUserContext().getId());
        }
        return result;
    }

    @Override
    public int deleteRole(String id) {
        int result = 0;


        SysRole role = sysRoleMapper.selectByPrimaryKey(id);
        if (role != null) {

            // sysRoleMapper.deleteByPrimaryKey(id);
            role.setIsdeleted(1);
            sysRoleMapper.updateByPrimaryKey(role);

            sysRoleMapper.deleteFunsByRoleId(id);
            result = sysRoleMapper.deleteAllUserRolesByRoleId(id);
            if (result > 0) {
                iLogService.log("info",
                        "角色管理",
                        "删除成功-【" + id + "】-【" + role.getRolename() + "】",
                        iUserContextService.getUserContext().getId());
            }
        }
        return result;
    }

    @Override
    public int updateRole(SysRole sysRole) {
        SysRole sysRole1 = sysRoleMapper.selectByPrimaryKey(sysRole.getGuid());
        sysRole.setCreatetime(sysRole1.getCreatetime());
        sysRole.setIsdeleted(sysRole1.getIsdeleted());
        int result = sysRoleMapper.updateByPrimaryKey(sysRole);
        if (result > 0) {
            iLogService.log("info",
                    "角色管理",
                    "修改成功-【" + JSON.toJSONString(sysRole) + "】",
                    iUserContextService.getUserContext().getId());
        }
        return result;
    }

    @Override
    public int deleteAllRolesByUserId(String userId) {
        int result = sysRoleMapper.deleteAllRolesByUserId(userId);
        if (result > 0) {
            iLogService.log("info",
                    "角色管理",
                    "删除用户对应角色集合-【" + userId + "】",
                    iUserContextService.getUserContext().getId());
        }
        return result;
    }

    @Override
    public int deleteFunsByRoleId(String roleId) {
        int result = sysRoleMapper.deleteFunsByRoleId(roleId);
        if (result > 0) {
            iLogService.log("info",
                    "角色管理",
                    "删除角色对应权限集合-【" + roleId + "】",
                    iUserContextService.getUserContext().getId());
        }
        return result;
    }

    @Override
    public List<SysRole> findRoles(ApiQueryBase apiQueryBase) {
        return sysRoleMapper.find(apiQueryBase);
    }

    @Override
    public SysRole findOneRole(String id) {
        return sysRoleMapper.selectByPrimaryKey(id);
    }

    @Override
    public List<FunModel> findFunsByUserId(String userId) {
        return sysRoleMapper.findFunsByUserId(userId);
    }

    @Override
    public List<FunModel> findAllFunsByRoleId(String roleId) {
        List<FunModel> funModels = sysRoleMapper.findAllFunsByRoleId(roleId);
        List<FunModel> result = new ArrayList<FunModel>();

        //初始化根节点
        FunModel root = new FunModel();
        root.setId("root");
        root.setName("功能权限");
        root.setIsleaf(0);
        root.setChildren(new ArrayList<FunModel>());

        BuildFunTree(root, funModels);

        if (root.getChildren() != null && root.getChildren().size() != 0) {
            root.setIsleaf(0);
        } else {
            root.setIsleaf(1);
        }

        result.add(root);
        return result;
    }

    private void BuildFunTree(FunModel node, List<FunModel> funModels) {
        for (FunModel funModel :
                funModels) {
            if (funModel.getParentid() != null && funModel.getParentid().equals(node.getId())) {
                FunModel child = new FunModel();
                child.setId(funModel.getId());
                child.setName(funModel.getName());
                child.setParentid(funModel.getParentid());
                child.setChecked(funModel.isChecked());
                child.setChildren(new ArrayList<FunModel>());
                node.getChildren().add(child);

                //递归调用
                BuildFunTree(child, funModels);
                if (child.getChildren() != null && child.getChildren().size() != 0) {
                    child.setIsleaf(0);
                } else {
                    child.setIsleaf(1);
                }
            }

        }

    }

    @Override
    public int saveFuns(String roleId, List<FunModel> funModels) {

        int result = 0;
        //删除当前角色下的功能权限
        sysRoleMapper.deleteFunsByRoleId(roleId);

        //重新创建该角色下的功能权限
        for (FunModel funModel : funModels) {
            SysRoleFunMap sysRoleFunMap = new SysRoleFunMap();
            sysRoleFunMap.setGuid(UUID.randomUUID().toString());
            sysRoleFunMap.setRoleid(roleId);
            sysRoleFunMap.setFunid(funModel.getId());
            result += sysRoleFunMapMapper.insertSelective(sysRoleFunMap);
        }

        if (result >= 0) {
            iLogService.log("info",
                    "角色管理",
                    "角色【" + roleId + "】，权限集合保存-【" + JSON.toJSONString(funModels) + "】",
                    iUserContextService.getUserContext().getId());
        }

        return result;
    }
    //endregion

    //region << 框架菜单 >>

    /**
     * 查询菜单
     *
     * @param userId
     * @return
     */
    @Override
    public List<MenuModel> findMenus(String userId) {
        List<SysMenu> sysMenus = null;
        if (userId.equals("0")) {
            sysMenus = sysMenuMapper.findAll();
        } else {
            sysMenus = sysMenuMapper.find(userId);
        }

        List<MenuModel> menuModels = new ArrayList<MenuModel>();

        //初始化根节点
        MenuModel root = new MenuModel();
        root.setId("root");
        root.setMenuname("根节点");
        root.setNumber("");
        root.setChild(new ArrayList<MenuModel>());

        BuildMenuTree(root, sysMenus);

        if (root.getChild() != null && root.getChild().size() != 0) {
            root.setIsleaf(0);
        } else {
            root.setIsleaf(1);
        }

        menuModels.add(root);

        return menuModels;

    }

    private void BuildMenuTree(MenuModel node, List<SysMenu> sysMenus) {
        for (SysMenu sysMenu :
                sysMenus) {
            if (sysMenu.getParentmenuguid().equals(node.getId())) {
                MenuModel child = new MenuModel();
                child.setId(sysMenu.getGuid());
                child.setMenuname(sysMenu.getMenuname());
                child.setParentid(sysMenu.getParentmenuguid());
                child.setNumber(sysMenu.getMenuid());
                if (StringUtils.isNoneBlank(sysMenu.getMenuurl())) {
                    child.setPath(sysMenu.getMenuurl());
                } else {
                    child.setPath("");
                }
                child.setOrderindex(sysMenu.getMenuorder());
                child.setIcon(sysMenu.getMenuimgurl());
                child.setChild(new ArrayList<MenuModel>());
                node.getChild().add(child);

                BuildMenuTree(child, sysMenus);

                if (child.getChild() != null && child.getChild().size() != 0) {
                    child.setIsleaf(0);
                } else {
                    child.setIsleaf(1);
                }

            }

        }

    }

    //endregion

    //region << 用户登录 >>

    @Override
    public ApiResult login(String ename, String password, String isLogin, HttpServletRequest request,String isCookie,String uuid) throws Exception {
        ApiResult<String> result = null;
        String ip = request.getHeader("x-forwarded-for");
        if (ip == null || ip.length() == 0) {
            ip = request.getRemoteAddr();
        }
        //System.out.println(ip);
        if (!StringUtils.isNoneBlank(ename)) {
            result = new ApiResult(AppConstant.MSG_FAILURE, false, "请输入登录账号");
            return result;
        }

        if (!StringUtils.isNoneBlank(password)) {
            result = new ApiResult(AppConstant.MSG_FAILURE, false, "请输入登录密码");
            return result;
        }
        SysUser sysUser=sysUserMapper.selectByEName(ename);
        //判断用户非空,帐号大小写区分
        if ( null == sysUser || !ename.equals(sysUser.getEname())) {
            //判断ip地址是否超过三次
            LoginLogModel loginLogModel = new LoginLogModel();
            loginLogModel.setIp(ip);
            loginLogModel.setIsdeleted(0);
            sysUserMapper.insertSysLoginLog(loginLogModel);
            int times = sysUserMapper.selectByip(ip);
            result = new ApiResult(AppConstant.MSG_FAILURE, false, "用户名不存在", times + "");
            return result;
        }
        //找到该用户
        //判断是否是Cookie登录
        if(null != isCookie && isCookie.equals("true")){
            //从redis中取出字符串
            if(redisTemplate.opsForValue().size(uuid)==0){
                return new ApiResult(AppConstant.MSG_FAILURE, false, "请重新登录");
            }
            String rediscontent =(String) redisTemplate.opsForValue().get(uuid);
            //判读非空
            if(StringUtil.isEmpty(rediscontent)){
                return new ApiResult(AppConstant.MSG_FAILURE, false, "请输入登录账号");
            }
            //解密字符串
            String content=Des3Kit.decrypt(rediscontent);
//            System.out.println("解密出的字符串:"+content);
            String[] str=content.split(";");
            //判断时间戳
            if((new Date()).getTime()>Long.parseLong(str[2].trim())){
                return new ApiResult(AppConstant.MSG_FAILURE, false, "请重新登录");
            }
            //判断用户名
            SysUser sysUser1=sysUserMapper.selectByEName(str[0]);
            if(null == sysUser1 || !sysUser1.getEname().equals(str[0])){
               return new ApiResult(AppConstant.MSG_FAILURE, false, "用户名或密码错误");
            }
            //判断密码
            if(!sysUser1.getPwd().equals(str[1])){
                return new ApiResult(AppConstant.MSG_FAILURE, false, "用户名或密码错误");
            }
//            System.out.println("自动登录成功");
        }else{
            //非Cookie登录
            if (count(ename, password) < 1) {
                LoginLogModel loginLogModel = new LoginLogModel();
                loginLogModel.setUserid(sysUser.getGuid());
                loginLogModel.setIsdeleted(0);
                sysUserMapper.insertSysLoginLog(loginLogModel);
                int times = sysUserMapper.selectByUserid(sysUser.getGuid()) + sysUserMapper.selectByip(ip);
                result = new ApiResult(AppConstant.MSG_FAILURE, false, "用户名与密码不匹配", times + "");
                return result;
            }
        }

        List<SysMenu> userMenus = sysMenuMapper.find(sysUser.getGuid());
        UserContext userContext = new UserContext();
        userContext.setId(sysUser.getGuid());
        userContext.setUsername(sysUser.getEname());
        userContext.setName(sysUser.getCname());
        // add by wangwei 2017-06-29
        userContext.setOrgid(sysUser.getOrgid());
        if (userMenus != null && userMenus.size() > 0) {
            userContext.setMenupaths(new ArrayList<>());
            for (int i = 0; i < userMenus.size(); i++) {
                userContext.getMenupaths().add(userMenus.get(i).getMenuurl());
            }
        }
        //profileUserModel.setAvatar("https://timgsa.baidu.com/timg?image&quality=80&size=b9999_10000&sec=1488017572321&di=96bec9693bfce743bdb4c823942e89e3&imgtype=0&src=http%3A%2F%2Fwww.icosky.com%2Ficon%2Fpng%2FSystem%2FScrap%2FAdministrator%25202.png");
        //System.out.println(md5Pwd);
        //判断是否记住下次自动登录
        if(StringUtil.isNotEmpty(isLogin) && isLogin.equals("true")){
            //生成uuid
            uuid=UUID.randomUUID().toString();
            //用户名+密码+时间戳
            String redisContent=sysUser.getEname()+";"+sysUser.getPwd()+";"+(new Date().getTime()+7*24*60*60*1000);//7*24*60*60*1000
            //进行对称加密
            String token=Des3Kit.encrypt(redisContent);
            //放入redis中
            redisTemplate.opsForValue().set(uuid,token,7,TimeUnit.DAYS);
        }
        result = new ApiResult(AppConstant.MSG_SUCCESS, true, uuid, userContext);
        //去除该ip地址登录的日志
        sysUserMapper.updateByIp(ip);
        //去除该用户的登录日志
        sysUserMapper.updateByUserid(sysUser.getGuid());
        //记录Session
        iUserContextService.setUserContext(userContext);

        //记录登录日志
        iLogService.log("info",
                "登录",
                "登录成功-【" + JSON.toJSONString(userContext) + "】",
                iUserContextService.getUserContext().getId());

        // add by wangwei 2017-03-27
        userContext.setOrgid(sysUser.getOrgid());

        return result;
    }

//    @Override
//    public UserContext getUserContext(String ename, String password) {
//
//
//        UserContext userContext = new UserContext();
//        userContext.setId("0");
//        userContext.setUsername("admin");
//        userContext.setName("管理员");
//        //userContext.setAvatar("https://timgsa.baidu.com/timg?image&quality=80&size=b9999_10000&sec=1488017572321&di=96bec9693bfce743bdb4c823942e89e3&imgtype=0&src=http%3A%2F%2Fwww.icosky.com%2Ficon%2Fpng%2FSystem%2FScrap%2FAdministrator%25202.png");
//        return userContext;
//    }

    public int count(String ename, String password) throws Exception {
        String encrypt = DesUtils.encrypt(password);
        return sysUserMapper.selectCountByEnameAndPwd(ename, encrypt);
    }

    //endregion

    // region << 全局配置 >>

    public int saveConfig(GlobalConfigModel globalConfigModel) {
        int result = 0;

        SysConfig sysConfig = sysConfigMapper.selectByPrimaryKey(GLOBAL_CONFIG_ID);
        if (sysConfig == null) {
            sysConfig = new SysConfig();
            sysConfig.setGuid(GLOBAL_CONFIG_ID);
            sysConfig.setContent(JSON.toJSONString(globalConfigModel));
            result = sysConfigMapper.insert(sysConfig);
        } else {
            sysConfig.setContent(JSON.toJSONString(globalConfigModel));
            result = sysConfigMapper.updateByPrimaryKeySelective(sysConfig);
        }


        return result;
    }

    public GlobalConfigModel findGlobalConfig() {
        GlobalConfigModel globalConfigModel = null;
        SysConfig sysConfig = sysConfigMapper.selectByPrimaryKey(GLOBAL_CONFIG_ID);
        globalConfigModel = JSON.parseObject(sysConfig.getContent(), GlobalConfigModel.class);
        return globalConfigModel;
    }

    // endregion

    @Override
    public ApiCode applyResetPwd(String account) {
        ApiCode apiCode=ApiCode.APP_120502;
        SysUser sysUser=sysUserMapper.selectByEName(account);
        //System.out.println("account:"+account);
        if(null==account || account.equals(" ") ){
            apiCode=ApiCode.APP_121510;
            return apiCode;
        }
        if(null == sysUser || !account.equals(sysUser.getEname())){
            //账户不存在
            apiCode=ApiCode.APP_121508;
            return apiCode;
        }
        ResetPasswordModel resetPasswordModel=sysUserMapper.selectResetPwdByUserid(sysUser.getGuid());
        if (null!=resetPasswordModel){
            //重复提交申请
            apiCode=ApiCode.APP_121509;
            return apiCode;
        }
        int result=sysUserMapper.insertResetPwd(sysUser.getGuid());
        return apiCode;
    }

    /**
     * 密码重置
     * @param userid
     * @return
     */
    @Override
    public ApiCode submitResetPwd(String userid) throws Exception {
        ApiCode apiCode=ApiCode.APP_120503;
        SysUser user = sysUserMapper.selectByPrimaryKey(userid);
        if (null != user) {
            //设置默认密码
            String pwd="123456";
            user.setPwd(DesUtils.encrypt(pwd));
            sysUserMapper.updateByPrimaryKey(user);
            ResetPasswordModel resetPasswordModel=sysUserMapper.selectResetPwdByUserid(userid);
            if(null != resetPasswordModel){
                //修改申请的信息
                resetPasswordModel.setIsdefault(1);
                sysUserMapper.updateResetPwd(resetPasswordModel);
            }
        }else{
            //用户不存在
            apiCode=ApiCode.APP_121508;
            return apiCode;
        }
        return apiCode;
    }

    @Override
    public List<UserResetPwdModel> findResertPwd(ApiQueryBase queryBase,HttpServletRequest request) {
        return sysUserMapper.selectResertPwd(queryBase);
    }

    @Override
    public List<FunBtnModel> findOnlyBtnFunsByUserId(String userId) {
        return sysRoleMapper.findOnlyBtnFunsByUserId(userId);
    }
}